package xp2p.inter.server;

import java.io.IOException;
import java.io.InputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.OutputStream;
import java.net.Socket;

import p2p.infra.PeerContext;

import xp2p.inter.msg.FinishedConversationException;
import xp2p.inter.msg.FinishedMessage;
import xp2p.inter.msg.Ping;
import xp2p.inter.msg.Pong;
import xp2p.inter.msg.SendMessage;

/**
 * The Class ClientHandler.
 */
public class ClientHandler implements Runnable
{
	private Socket client;
	private ObjectInputStream in;
	private ObjectOutputStream out;
	private HandlerFactory factory;
	
	public ClientHandler(Socket client, HandlerFactory factory)
	{
		this.client = client;
		this.factory = factory;		
	}

	@Override
	public void run()
	{
		while (true)
		{
			try
			{
				if (client.isClosed())
				{
					return;
				}
				InputStream stream = client.getInputStream();
				in = new ObjectInputStream(stream);
				Object message = in.readObject();
				OutputStream stream2 = client.getOutputStream();
				out = new ObjectOutputStream(stream2);				
				Handle(message);
				client.close();
				return;
			} catch (IOException e)
			{				
				e.printStackTrace();
			} catch (ClassNotFoundException e)
			{				
				e.printStackTrace();
			} catch (FinishedConversationException e)
			{
				e.printStackTrace();
				try
				{
					client.close();
				} catch (IOException e1)				
				{					
					e1.printStackTrace();
				}
				return;
			}
		}
	}

	private void Handle(Object message) throws FinishedConversationException, IOException
	{
		if (message.getClass().equals(FinishedMessage.class))			
		{
			out.writeObject(new FinishedMessage());
			throw new FinishedConversationException();
		}
		if (message.getClass().equals(Ping.class))			
		{
			out.writeObject(new Pong());
		}		
		if (message.getClass().equals(SendMessage.class))
		{
			PeerContext.GetCurrentApp().Handle((SendMessage)message);
		}
		
	}
}
